<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>KgBackTrace类说明文档</title>
    <style>
        body {
            font-family: 'Microsoft YaHei', Arial, sans-serif;
            line-height: 1.6;
            color: #333;
            max-width: 1200px;
            margin: 0 auto;
            padding: 20px;
        }
        h1 {
            color: #0066cc;
            border-bottom: 2px solid #0066cc;
            padding-bottom: 10px;
        }
        h2 {
            color: #0066cc;
            border-bottom: 1px solid #ddd;
            padding-bottom: 5px;
            margin-top: 30px;
        }
        h3 {
            color: #333;
            margin-top: 20px;
        }
        pre {
            background-color: #f5f5f5;
            padding: 10px;
            border-radius: 5px;
            overflow-x: auto;
        }
        code {
            font-family: Consolas, Monaco, 'Andale Mono', monospace;
            background-color: #f5f5f5;
            padding: 2px 4px;
            border-radius: 3px;
        }
        table {
            border-collapse: collapse;
            width: 100%;
            margin: 20px 0;
        }
        th, td {
            border: 1px solid #ddd;
            padding: 8px 12px;
            text-align: left;
        }
        th {
            background-color: #f2f2f2;
        }
        .note {
            background-color: #f8f9fa;
            border-left: 4px solid #0066cc;
            padding: 10px 15px;
            margin: 20px 0;
        }
        .warning {
            background-color: #fff3cd;
            border-left: 4px solid #ffc107;
            padding: 10px 15px;
            margin: 20px 0;
        }
        .function {
            margin-bottom: 30px;
        }
        .function h3 {
            color: #0066cc;
            margin-bottom: 10px;
        }
        .parameter {
            margin-left: 20px;
        }
        .signal-table {
            margin-top: 15px;
        }
    </style>
</head>
<body>
    <h1>KgBackTrace类说明文档</h1>

    <h2>1. 类概述</h2>
    <p>KgBackTrace是一个用于处理程序异常的工具类，主要功能是捕获程序运行过程中的崩溃信号，并记录崩溃时的堆栈信息，便于开发人员分析和定位问题。该类通过Linux信号处理机制，在程序发生异常时自动收集堆栈跟踪信息并保存到日志文件中。</p>

    <div class="note">
        <p><strong>注意：</strong>KgBackTrace类需要在程序启动时进行初始化，以确保能够捕获程序运行过程中的异常信号。</p>
    </div>

    <h2>2. 头文件声明</h2>
    <pre><code>#ifndef KG_BACK_TRACE_H
#define KG_BACK_TRACE_H

#include &lt;QtCore&gt;

//初始化异常处理
extern void InitBackTrace();
//异常的文字描述
extern QString SignalText(int iSignalNo);
//获取异常堆栈信息
extern void BackTraceHandler(int iSignalNo);
//记录异常堆栈信息到/userdata/bams/log/dump_***.txt
extern void WriteBackTrace(const QString& strText);

#endif //KG_BACK_TRACE_H</code></pre>

    <h2>3. 主要功能</h2>
    <p>KgBackTrace类提供以下主要功能：</p>
    <ul>
        <li>初始化信号处理机制，捕获程序异常</li>
        <li>获取异常信号的文字描述</li>
        <li>收集程序崩溃时的堆栈信息</li>
        <li>将异常信息保存到日志文件中</li>
    </ul>

    <h2>4. 函数详解</h2>

    <div class="function">
        <h3>4.1 InitBackTrace()</h3>
        <p><strong>功能描述：</strong>初始化异常处理机制，注册信号处理函数。</p>
        <p><strong>函数原型：</strong><code>void InitBackTrace()</code></p>
        <p><strong>参数：</strong>无</p>
        <p><strong>返回值：</strong>无</p>
        <p><strong>使用示例：</strong></p>
        <pre><code>// 在程序启动时调用
int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    InitBackTrace(); // 初始化异常处理
    
    // 程序其他初始化代码...
    
    return a.exec();
}</code></pre>
        <p><strong>实现细节：</strong>该函数通过调用signal()函数注册各种异常信号的处理函数，当程序发生异常时，会自动调用BackTraceHandler函数处理异常。目前注册了以下信号：</p>
        <table class="signal-table">
            <tr>
                <th>信号</th>
                <th>描述</th>
                <th>状态</th>
            </tr>
            <tr>
                <td>SIGINT (2)</td>
                <td>硬中断 Interactive attention signal</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGILL (4)</td>
                <td>非法指令 illegal instruction-invalid function image</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGABRT (6)</td>
                <td>异常终止 abnormal termination triggered by abort call</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGFPE (8)</td>
                <td>浮点异常 floating point exception</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGSEGV (11)</td>
                <td>段错误 segment violation</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGTERM (15)</td>
                <td>杀进程 Software termination signal from kill</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>SIGXCPU (24)</td>
                <td>CPU时间限制超出 CPU time limit exceeded</td>
                <td>已启用</td>
            </tr>
            <tr>
                <td>其他信号</td>
                <td>代码中已注释，可根据需要启用</td>
                <td>未启用</td>
            </tr>
        </table>
    </div>

    <div class="function">
        <h3>4.2 SignalText(int iSignalNo)</h3>
        <p><strong>功能描述：</strong>获取异常信号的文字描述。</p>
        <p><strong>函数原型：</strong><code>QString SignalText(int iSignalNo)</code></p>
        <p><strong>参数：</strong></p>
        <div class="parameter">
            <p><code>iSignalNo</code> - 信号编号，如SIGINT(2)、SIGSEGV(11)等</p>
        </div>
        <p><strong>返回值：</strong>返回信号对应的文字描述</p>
        <p><strong>使用示例：</strong></p>
        <pre><code>// 获取SIGSEGV信号的描述
QString description = SignalText(SIGSEGV);
// 输出: "段错误 segment violation"</code></pre>
        <p><strong>实现细节：</strong>该函数通过switch-case语句，根据传入的信号编号返回对应的文字描述。如果传入的信号编号不在预定义的范围内，则返回"未知错误信号"。</p>
    </div>

    <div class="function">
        <h3>4.3 BackTraceHandler(int iSignalNo)</h3>
        <p><strong>功能描述：</strong>异常信号处理函数，收集堆栈信息并保存到日志文件。</p>
        <p><strong>函数原型：</strong><code>void BackTraceHandler(int iSignalNo)</code></p>
        <p><strong>参数：</strong></p>
        <div class="parameter">
            <p><code>iSignalNo</code> - 触发的信号编号</p>
        </div>
        <p><strong>返回值：</strong>无</p>
        <p><strong>实现细节：</strong>该函数是信号处理的核心函数，当程序发生异常时会自动调用。主要执行以下步骤：</p>
        <ol>
            <li>记录异常发生的时间、信号值和原因</li>
            <li>使用backtrace()函数获取当前的函数调用堆栈</li>
            <li>使用backtrace_symbols()函数将地址转换为符号信息</li>
            <li>将收集到的信息格式化并保存到日志文件</li>
            <li>调用exit(1)终止程序，防止无限循环</li>
        </ol>
        <div class="warning">
            <p><strong>警告：</strong>该函数在处理完异常信息后会调用exit(1)终止程序，以防止程序在不稳定状态下继续运行导致更严重的问题。</p>
        </div>
    </div>

    <div class="function">
        <h3>4.4 WriteBackTrace(const QString& strText)</h3>
        <p><strong>功能描述：</strong>将异常堆栈信息写入日志文件。</p>
        <p><strong>函数原型：</strong><code>void WriteBackTrace(const QString& strText)</code></p>
        <p><strong>参数：</strong></p>
        <div class="parameter">
            <p><code>strText</code> - 要写入日志文件的文本内容</p>
        </div>
        <p><strong>返回值：</strong>无</p>
        <p><strong>实现细节：</strong>该函数将异常信息写入指定的日志文件中。日志文件路径为：/userdata/bams/log/dump_[应用程序名称].txt。如果文件打开失败，函数将直接返回，不做任何处理。</p>
    </div>

    <h2>5. 使用示例</h2>
    <p>以下是KgBackTrace类的典型使用方式：</p>

    <pre><code>// 在程序的main函数中初始化异常处理
#include "KgBackTrace.h"

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    // 初始化异常处理，必须在程序启动时调用
    InitBackTrace();

    // 程序的其他初始化和主循环代码
    // ...

    return a.exec();
}</code></pre>

    <h2>6. 异常日志格式</h2>
    <p>当程序发生异常时，KgBackTrace会生成类似以下格式的日志：</p>

    <pre><code>
异常发送时间:2024-05-15 14:30:22.345
异常信号值:11
异常信号原因:段错误 segment violation
堆栈地址数:15
15 ./xnbmsio(+0x12345) [0x7f1234567890]
14 ./xnbmsio(+0x23456) [0x7f1234578901]
13 /lib/x86_64-linux-gnu/libc.so.6(+0x34567) [0x7f1234589012]
...
</code></pre>

    <p>日志文件中的每一行堆栈信息包含以下内容：</p>
    <ul>
        <li>序号：从大到小排列，表示调用深度</li>
        <li>模块名称：如./xnbmsio、libc.so.6等</li>
        <li>偏移地址：如(+0x12345)</li>
        <li>内存地址：如[0x7f1234567890]</li>
    </ul>

    <h2>7. 注意事项</h2>
    <ul>
        <li>KgBackTrace类需要在程序启动时进行初始化，否则无法捕获异常</li>
        <li>该类依赖于Linux的信号处理机制和backtrace相关函数，不适用于Windows平台</li>
        <li>异常处理函数会终止程序运行，因此不适合用于需要程序继续运行的场景</li>
        <li>为了获取更详细的堆栈信息，建议在编译时添加调试信息（如使用-g选项）</li>
        <li>日志文件路径固定为/userdata/bams/log/目录，使用前请确保该目录存在且有写入权限</li>
    </ul>

    <h2>8. 相关类</h2>
    <ul>
        <li><strong>KgLogFile</strong>：日志文件类，提供日志记录功能</li>
        <li><strong>KgGlobalData</strong>：全局数据类，管理应用程序全局数据</li>
    </ul>

    <div class="note">
        <p>文档创建日期：2024年5月</p>
        <p>适用版本：BA-10-V3.8.0</p>
    </div>
</body>
</html>